﻿//+-------------------------------------------------------------------------------------------------------------------------------------------------------
//
//Description: OperatingSystemProfileViewModel
//Author: Aravind Ramarathinam (aravr@microsoft.com)
//Copyright © Microsoft Corporation
//Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. 
//You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0 
//
//THIS CODE IS PROVIDED *AS IS* BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED, 
//INCLUDING WITHOUT LIMITATION ANY IMPLIED WARRANTIES OR CONDITIONS OF TITLE, FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABLITY OR NON-INFRINGEMENT. 
//See the Apache Version 2.0 License for specific language governing permissions and limitations under the License.
// 
//--------------------------------------------------------------------------------------------------------------------------------------------------------

using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using VmroleAuthor.Models;

namespace VmroleAuthor.ViewModels
{
    public class OperatingSystemProfileViewModel : TreeViewItemViewModel, IDataErrorInfo,  IProduceValidationResults
    {
        private readonly VmRoleResourceDefinitionViewModel vmRoleResourceDefinitionViewModel;
        private OperatingSystemProfile operatingSystemProfile;      

        private const string Windows = "Windows";
        private const string Linux = "Linux";
        private const string None = "None - customization not required";
        private const string Workgroup = "Workgroup";
        private const string JoinDomain = "JoinDomain";
        private readonly List<string> oslist = new List<string> { Windows, Linux, None };
        private readonly List<string> windowsOsCustomizationOptions = new List<string> {Workgroup, JoinDomain};
        private string selectedOs;
        private string selectedWindowsOsCustomizationOption;
        private bool isWorkgroup;

        private StringParameterizableProperty computerNamePattern;
        private StringParameterizableProperty timeZone;
        private CredentialParameterizableProperty adminCredential;
        private StringParameterizableProperty workgroupName;
        private StringParameterizableProperty domainToJoin;
        private CredentialParameterizableProperty domainJoinCredentials;
        private StringParameterizableProperty dnsDomainName;
        private StringParameterizableProperty sshPublicKey;

        public static class PropertyNames
        {
            public const string Summary = "Summary";
            public const string SelectedOperatingSystem = "SelectedOperatingSystem";
            public const string SelectedWindowsOsCustomizationOption = "SelectedWindowsOsCustomizationOption"; 
            // Common
            public const string ComputerNamePattern = "ComputerNamePattern";
            public const string TimeZone = "TimeZone";
            public const string AdminCredential = "AdminCredential";    
            //Windows
            public const string WorkgroupName = "WorkgroupName";
            public const string DomainToJoin = "DomainToJoin";
            public const string DomainJoinCredentials = "DomainJoinCredentials";
            //Linux
            public const string DNSDomainName = "DNSDomainName";
            public const string SSHPublicKey = "SSHPublicKey";
        }

        public OperatingSystemProfileViewModel(
            OperatingSystemProfile  operatingSystemProfile,
            VmRoleResourceDefinitionViewModel resourceDefinitionViewModel)
            : base(resourceDefinitionViewModel, true)
        {
            if (operatingSystemProfile == null)
            {
                operatingSystemProfile = new OperatingSystemProfile();
            }
            this.operatingSystemProfile = operatingSystemProfile;
            this.vmRoleResourceDefinitionViewModel = resourceDefinitionViewModel;          
            if (this.operatingSystemProfile == null)
            {
                this.selectedOs = None;
            }
            else if ((this.operatingSystemProfile.WindowsOperatingSystemProfile != null)&&(this.operatingSystemProfile.LinuxOperatingSystemProfile == null))
            {
                this.selectedOs = Windows;
                this.isWorkgroup = true;
                if (this.operatingSystemProfile.WindowsOperatingSystemProfile.WorkgroupName != null)
                {
                    this.selectedWindowsOsCustomizationOption = Workgroup;                  
                }
                else if (this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin != null)
                {
                    this.selectedWindowsOsCustomizationOption = JoinDomain;
                    this.isWorkgroup = false;
                }
            }
            else if ((this.operatingSystemProfile.LinuxOperatingSystemProfile != null)&&(this.operatingSystemProfile.WindowsOperatingSystemProfile == null))
            {
                this.selectedOs = Linux;
            }         
            this.ValidationResults = new ObservableCollection<CloudServiceModelValidationResult>();         

            if (this.vmRoleResourceDefinitionViewModel.IsNewResdefCreatedByTheTool)
            {
                this.AdminCredential.PropertyValue = ParametersViewModel.AutoGenerateMoniker;
                this.TimeZone.PropertyValue = ParametersViewModel.AutoGenerateMoniker;
                this.ComputerNamePattern.PropertyValue = ParametersViewModel.AutoGenerateMoniker;
                this.AdminCredential.PropertyValue = ParametersViewModel.AutoGenerateMoniker;
                this.WorkgroupName.PropertyValue = ParametersViewModel.AutoGenerateMoniker;
            }
        }

        public string Summary
        {
            get
            {                                
                return "Operating System Profile";
            }
        }



        public List<string> AvailableOperatingSystems
        {
            get
            {                
                return oslist;
            }
        }

        public string SelectedOperatingSystem
        {
            get { return this.selectedOs; }
            set
            {
                if ((value == null) || (string.Equals(value, this.selectedOs, StringComparison.Ordinal))) return;
                this.selectedOs = value;

                bool windows = false;
                bool linux = false;
                bool noCustomization = false;
                if (string.Equals(this.selectedOs, Windows, StringComparison.Ordinal))
                {
                    if (this.operatingSystemProfile == null)
                    {
                        this.operatingSystemProfile = new OperatingSystemProfile();
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinition.IntrinsicSettings.OperatingSystemProfile = this.operatingSystemProfile;
                    }
                    if (this.operatingSystemProfile.WindowsOperatingSystemProfile == null)
                    {
                        this.operatingSystemProfile.WindowsOperatingSystemProfile = new WindowsOperatingSystemProfile();
                    }
                    windows = true;
                }
                else if (string.Equals(this.selectedOs, Linux, StringComparison.Ordinal))
                {
                    if (this.operatingSystemProfile == null)
                    {
                        this.operatingSystemProfile = new OperatingSystemProfile();
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinition.IntrinsicSettings.OperatingSystemProfile = this.operatingSystemProfile;
                    }
                    if (this.operatingSystemProfile.LinuxOperatingSystemProfile == null)
                    {
                        this.operatingSystemProfile.LinuxOperatingSystemProfile = new LinuxOperatingSystemProfile();
                    }
                    linux = true;
                }
                else
                {
                    noCustomization = true;
                    this.ComputerNamePattern.IsRequired = false;
                    this.ComputerNamePattern.PropertyValue = null;
                    this.TimeZone.IsRequired = false;
                    this.TimeZone.PropertyValue = null;
                    this.AdminCredential.IsRequired = false;
                    this.AdminCredential.PropertyValue = null;
                }              

                if (windows || noCustomization)
                {
                    this.DNSDomainName.IsRequired = false;
                    this.DNSDomainName.PropertyValue = null;
                    this.SSHPublicKey.IsRequired = false;
                    this.SSHPublicKey.PropertyValue = null;
                    if (this.operatingSystemProfile != null)
                    {
                        this.operatingSystemProfile.LinuxOperatingSystemProfile = null;
                    }                   
                }

                if ( linux || noCustomization)
                {
                    this.WorkgroupName.IsRequired = false;
                    this.WorkgroupName.PropertyValue = null;
                    this.DomainToJoin.IsRequired = false;
                    this.DomainToJoin.PropertyValue = null;
                    this.DomainJoinCredentials.IsRequired = false;
                    this.DomainJoinCredentials.PropertyValue = null;
                    this.selectedWindowsOsCustomizationOption = null;
                    if (this.operatingSystemProfile != null)
                    {
                        this.operatingSystemProfile.WindowsOperatingSystemProfile = null;           
                    }                                          
                }
                if (noCustomization)
                {
                    this.operatingSystemProfile = null;
                    this.vmRoleResourceDefinitionViewModel.ResourceDefinition.IntrinsicSettings.OperatingSystemProfile = null;
                }
                                      
                this.OnPropertyChanged(PropertyNames.SelectedOperatingSystem);
                this.OnPropertyChanged(PropertyNames.SelectedWindowsOsCustomizationOption);
                this.OnPropertyChanged("IsOSCustomized");
                this.OnPropertyChanged("IsWindows");
                this.OnPropertyChanged("IsLinux");
                this.OnPropertyChanged("IsWorkGroup");
                this.OnPropertyChanged("IsDomain"); 
                this.OnPropertyChanged(PropertyNames.ComputerNamePattern);
                this.OnPropertyChanged(PropertyNames.TimeZone);
                this.OnPropertyChanged(PropertyNames.AdminCredential ); 
                this.OnPropertyChanged(PropertyNames.WorkgroupName);
                this.OnPropertyChanged(PropertyNames.DomainToJoin);
                this.OnPropertyChanged(PropertyNames.DomainJoinCredentials);
                this.OnPropertyChanged(PropertyNames.DNSDomainName);
                this.OnPropertyChanged(PropertyNames.SSHPublicKey);
            }
        }        
        public List<string> AvailableWindowsOsCustomizationOptions 
        {
            get
            {
                return windowsOsCustomizationOptions;
            }
        }

        public string SelectedWindowsOsCustomizationOption
        {
            get { return this.selectedWindowsOsCustomizationOption; }
            set
            {
                if ((value == null) || (string.Equals(value, this.selectedWindowsOsCustomizationOption, StringComparison.Ordinal))) return;
                this.selectedWindowsOsCustomizationOption = value;

                if (this.operatingSystemProfile == null)
                {
                    this.operatingSystemProfile = new OperatingSystemProfile();
                    this.vmRoleResourceDefinitionViewModel.ResourceDefinition.IntrinsicSettings.OperatingSystemProfile = this.operatingSystemProfile;
                }
                if (this.operatingSystemProfile.WindowsOperatingSystemProfile == null)
                {
                    this.operatingSystemProfile.WindowsOperatingSystemProfile = new WindowsOperatingSystemProfile();
                }               
                this.selectedOs = Windows;
                this.DNSDomainName.IsRequired = false;
                this.DNSDomainName.PropertyValue = null;
                this.SSHPublicKey.IsRequired = false;
                this.SSHPublicKey.PropertyValue = null;
                this.operatingSystemProfile.LinuxOperatingSystemProfile = null;

                if (string.Equals(this.selectedWindowsOsCustomizationOption, Workgroup, StringComparison.Ordinal))
                {                   
                    this.DomainToJoin.IsRequired = false;
                    this.DomainToJoin.PropertyValue = null;
                    this.DomainJoinCredentials.IsRequired = false;
                    this.DomainJoinCredentials.PropertyValue = null;
                    this.isWorkgroup = true;
                    this.WorkgroupName.IsRequired = true;
                    this.WorkgroupName.PropertyValue = null;     
                    this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin = null;                                   
                }
                else if (string.Equals(this.selectedWindowsOsCustomizationOption,JoinDomain, StringComparison.Ordinal))
                {
                    this.isWorkgroup = false;                  
                    if (this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin == null)
                    {
                        this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin = new DomainJoin();
                    }                                     
                    this.WorkgroupName.IsRequired = false;
                    this.WorkgroupName.PropertyValue = null;
                    this.operatingSystemProfile.WindowsOperatingSystemProfile.WorkgroupName = null;
                    this.DomainToJoin.IsRequired = true;
                    this.DomainJoinCredentials.IsRequired = true;
                    this.DomainToJoin.PropertyValue = null;                    
                    this.DomainJoinCredentials.PropertyValue = null;                    
                }               

                this.OnPropertyChanged(PropertyNames.SelectedOperatingSystem);
                this.OnPropertyChanged(PropertyNames.SelectedWindowsOsCustomizationOption);
                this.OnPropertyChanged("IsOSCustomized");
                this.OnPropertyChanged("IsWindows");
                this.OnPropertyChanged("IsLinux");
                this.OnPropertyChanged("IsWorkGroup");
                this.OnPropertyChanged("IsDomain"); 
                this.OnPropertyChanged(PropertyNames.WorkgroupName);
                this.OnPropertyChanged(PropertyNames.DomainToJoin);                
                this.OnPropertyChanged(PropertyNames.DomainJoinCredentials);
            }
        }

        public bool IsOSCustomized
        {
            get { return this.operatingSystemProfile != null; }
        }

        public bool IsWindows
        {
            get { return this.operatingSystemProfile != null && this.operatingSystemProfile.WindowsOperatingSystemProfile != null; }
        }

        public bool IsLinux
        {
            get { return this.operatingSystemProfile != null && this.operatingSystemProfile.LinuxOperatingSystemProfile != null; }
        }

        public bool IsWorkGroup
        {
            get { return this.IsWindows && this.isWorkgroup; }
        }

        public bool IsDomain
        {
            get { return this.IsWindows && !this.isWorkgroup; }
        }

        public StringParameterizableProperty ComputerNamePattern
        {
            get
            {
                if (this.computerNamePattern == null)
                {                   
                    Func<string> paramValueGetter = () => this.operatingSystemProfile != null ? this.operatingSystemProfile.ComputerNamePattern : null;
                    Action<string> paramValueSetter = delegate(string value) { if (this.operatingSystemProfile != null) this.operatingSystemProfile.ComputerNamePattern = value; };
                    Func<string> autoParamNameGetter = () => ParametersViewModel.VMRolePrefix + PropertyNames.ComputerNamePattern;
                    ViewDefParamInfo viewDefParamInfo = new ViewDefParamInfo
                    {                        
                        ViewDefParameterType = ViewDefParameterType.ComputerNamePattern,
                        DefaultInitialValue = "MyMachine###",
                        DefaultEnglishLabelText = "Compute name pattern",
                        MinLength = 1,
                        MaxLength = 15
                    };

                    this.computerNamePattern = new StringParameterizableProperty(
                        PropertyNames.ComputerNamePattern,
                        paramValueGetter,
                        paramValueSetter,
                        autoParamNameGetter,
                        ParameterType.String,
                        "Compute name pattern",
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinitionParametersViewModel,
                        false,
                        viewDefParamInfo);
                }
                return this.computerNamePattern;
            }
        }

        public StringParameterizableProperty TimeZone
        {
            get
            {
                if (this.timeZone == null)
                {
                    Func<string> paramValueGetter = () => this.operatingSystemProfile != null ? this.operatingSystemProfile.TimeZone : null;
                    Action<string> paramValueSetter = delegate(string value) { if (this.operatingSystemProfile != null) this.operatingSystemProfile.TimeZone = value; };
                    Func<string> autoParamNameGetter = () => ParametersViewModel.VMRolePrefix + PropertyNames.TimeZone;
                    ViewDefParamInfo viewDefParamInfo = new ViewDefParamInfo
                    {
                        IsRecommendedToBeParameterized = true,
                        ViewDefParameterType = ViewDefParameterType.OSTimeZone,
                        DefaultInitialValue = "Pacific Standard Time",
                        DefaultEnglishLabelText = "Time zone"
                    };

                    this.timeZone = new StringParameterizableProperty(
                        PropertyNames.TimeZone,
                        paramValueGetter,
                        paramValueSetter,
                        autoParamNameGetter,
                        ParameterType.String,
                        "Time zone",
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinitionParametersViewModel,
                        false,
                        viewDefParamInfo);
                }
                return this.timeZone;
            }
        }


        public CredentialParameterizableProperty AdminCredential
        {
            get
            {
                if (this.adminCredential == null)
                {
                    Func<string> paramValueGetter = () => this.operatingSystemProfile != null ? this.operatingSystemProfile.AdminCredential : null;
                    Action<string> paramValueSetter = delegate(string value) { if (this.operatingSystemProfile != null) this.operatingSystemProfile.AdminCredential = value; };
                    Func<string> autoParamNameGetter = () => ParametersViewModel.VMRolePrefix + PropertyNames.AdminCredential;
                    ViewDefParamInfo viewDefParamInfo = new ViewDefParamInfo
                    {
                        IsRecommendedToBeParameterized = true,
                        ViewDefParameterType = ViewDefParameterType.Credential,                       
                        DefaultEnglishLabelText = "Administrator credential"
                    };

                    this.adminCredential = new CredentialParameterizableProperty(
                        PropertyNames.AdminCredential,
                        paramValueGetter,
                        paramValueSetter,
                        autoParamNameGetter,
                        ParameterType.Credential,
                        "Administrator credential",
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinitionParametersViewModel,
                        false,
                        viewDefParamInfo);
                }
                return this.adminCredential;
            }
        }


        public StringParameterizableProperty WorkgroupName
        {
            get
            {
                if (this.workgroupName == null)
                {
                    Func<string> paramValueGetter = () => this.operatingSystemProfile != null && this.operatingSystemProfile.WindowsOperatingSystemProfile != null ? this.operatingSystemProfile.WindowsOperatingSystemProfile.WorkgroupName : null;
                    Action<string> paramValueSetter = delegate(string value) { if (this.operatingSystemProfile != null && this.operatingSystemProfile.WindowsOperatingSystemProfile != null) this.operatingSystemProfile.WindowsOperatingSystemProfile.WorkgroupName = value; };
                    Func<string> autoParamNameGetter = () => ParametersViewModel.VMRolePrefix + PropertyNames.WorkgroupName;
                    ViewDefParamInfo viewDefParamInfo = new ViewDefParamInfo
                    {
                        ViewDefParameterType = ViewDefParameterType.String,
                        DefaultEnglishLabelText = "Workgroup name"
                    };

                    this.workgroupName = new StringParameterizableProperty(
                        PropertyNames.WorkgroupName,
                        paramValueGetter,
                        paramValueSetter,
                        autoParamNameGetter,
                        ParameterType.String,
                        "Workgroup name",
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinitionParametersViewModel,
                        this.IsWorkGroup,
                        viewDefParamInfo);
                }
                return this.workgroupName;
            }
        }
      
        public StringParameterizableProperty DomainToJoin
        {
            get
            {
                if (this.domainToJoin == null)
                {
                    Func<string> paramValueGetter = () =>
                        (this.IsWindows && !this.isWorkgroup && this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin != null)
                         ? this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin.DomainToJoin : null;
                    Action<string> paramValueSetter = delegate(string value)
                        {
                            if (this.IsWindows && !this.isWorkgroup && this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin != null)
                                this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin.DomainToJoin = value;
                        };
                    Func<string> autoParamNameGetter = () => ParametersViewModel.VMRolePrefix + PropertyNames.DomainToJoin;
                    ViewDefParamInfo viewDefParamInfo = new ViewDefParamInfo
                    {
                        IsRecommendedToBeParameterized = true,
                        ViewDefParameterType = ViewDefParameterType.String,
                        DefaultEnglishLabelText = "Domain to join"
                    };

                    this.domainToJoin = new StringParameterizableProperty(
                        PropertyNames.DomainToJoin,
                        paramValueGetter,
                        paramValueSetter,
                        autoParamNameGetter,
                        ParameterType.String,
                        "Domain to join",
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinitionParametersViewModel,
                        false,
                        viewDefParamInfo);
                }
                return this.domainToJoin;
            }
        }


        public CredentialParameterizableProperty DomainJoinCredentials
        {
            get
            {
                if (this.domainJoinCredentials == null)
                {
                    Func<string> paramValueGetter = () =>
                          (this.IsWindows  && !this.isWorkgroup && this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin != null)
                         ? this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin.DomainJoinCredentials : null;

                    Action<string> paramValueSetter = delegate(string value)
                        {
                            if (this.IsWindows && !this.isWorkgroup && this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin != null)                       
                                this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin.DomainJoinCredentials = value;
                        };
                    Func<string> autoParamNameGetter = () => ParametersViewModel.VMRolePrefix + PropertyNames.DomainJoinCredentials;
                    ViewDefParamInfo viewDefParamInfo = new ViewDefParamInfo
                    {
                        IsRecommendedToBeParameterized = true,
                        ViewDefParameterType = ViewDefParameterType.Credential,
                        DefaultEnglishLabelText = "Domain join credentials"
                    };

                    this.domainJoinCredentials = new CredentialParameterizableProperty(
                        PropertyNames.DomainJoinCredentials,
                        paramValueGetter,
                        paramValueSetter,
                        autoParamNameGetter,
                        ParameterType.Credential,
                        "Domain join credentials",
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinitionParametersViewModel,
                        false,
                        viewDefParamInfo);
                }
                return this.domainJoinCredentials;
            }            
        }
        
        public StringParameterizableProperty DNSDomainName
        {
            get
            {
                if (this.dnsDomainName == null)
                {
                    Func<string> paramValueGetter = () => this.IsLinux ? this.operatingSystemProfile.LinuxOperatingSystemProfile.DNSDomainName : null;
                    Action<string> paramValueSetter = delegate(string value) { if (this.IsLinux) this.operatingSystemProfile.LinuxOperatingSystemProfile.DNSDomainName = value; };
                    Func<string> autoParamNameGetter = () => ParametersViewModel.VMRolePrefix + PropertyNames.DNSDomainName;
                    ViewDefParamInfo viewDefParamInfo = new ViewDefParamInfo
                    {
                        ViewDefParameterType = ViewDefParameterType.String,
                        DefaultEnglishLabelText = "DNS domain name"
                    };

                    this.dnsDomainName = new StringParameterizableProperty(
                        PropertyNames.DNSDomainName,
                        paramValueGetter,
                        paramValueSetter,
                        autoParamNameGetter,
                        ParameterType.String,
                        "DNS domain name",
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinitionParametersViewModel,
                        false,
                        viewDefParamInfo);
                }
                return this.dnsDomainName;
            }
        }

        public StringParameterizableProperty SSHPublicKey
        {
            get
            {
                if (this.sshPublicKey == null)
                {
                    Func<string> paramValueGetter = () => this.IsLinux ? this.operatingSystemProfile.LinuxOperatingSystemProfile.SSHPublicKey : null;
                    Action<string> paramValueSetter = delegate(string value) { if (this.IsLinux) this.operatingSystemProfile.LinuxOperatingSystemProfile.SSHPublicKey = value; };
                    Func<string> autoParamNameGetter = () => ParametersViewModel.VMRolePrefix + PropertyNames.SSHPublicKey;
                    ViewDefParamInfo viewDefParamInfo = new ViewDefParamInfo
                    {
                        ViewDefParameterType = ViewDefParameterType.String,
                        DefaultEnglishLabelText = "SSH public key"
                    };

                    this.sshPublicKey = new StringParameterizableProperty(
                        PropertyNames.SSHPublicKey,
                        paramValueGetter,
                        paramValueSetter,
                        autoParamNameGetter,
                        ParameterType.String,
                        "SSH public key",
                        this.vmRoleResourceDefinitionViewModel.ResourceDefinitionParametersViewModel,
                        false,
                        viewDefParamInfo);
                }
                return this.sshPublicKey;
            }
        }

        
        public string this[string propertyName]
        {
            get
            {
                string error = null;
                switch (propertyName)
                {                   
                    case PropertyNames.SelectedOperatingSystem:
                        if (this.IsWindows & this.IsLinux)
                        {
                            error = "Specify either Windows or Linux Operating System profile. But not both";
                        }                        
                        break;                                     
                    case PropertyNames.SelectedWindowsOsCustomizationOption:
                        if (this.IsWindows &&
                           (this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin == null &&
                           !this.isWorkgroup))
                        {
                            error = "Specify atleast either Workgroup or DomainJoin.";
                        }
                        else if (this.IsWindows &&
                            this.operatingSystemProfile.WindowsOperatingSystemProfile.DomainJoin != null &&
                            this.operatingSystemProfile.WindowsOperatingSystemProfile.WorkgroupName != null)
                        {
                            error = "Specify either Workgroup or DomainJoin. But not both";
                        }
                        break;
                }
                return error;
            }
        }

        public string Error { get; set; }

        public ObservableCollection<CloudServiceModelValidationResult> ValidationResults { get; private set; }

        public void UpdateValidationResults()
        {
            this.IsExpanded = true;
            ModelValidationResultsHelper.UpdateValidationResults(this, typeof(PropertyNames));
            //Add any other cross-field validations error            
        }
    }
}
